package com.huangyi.adminservice.user.service.impl;

import cn.hutool.crypto.digest.DigestUtil;

import com.huangyi.adminservice.config.service.ISysDictionaryService;
import com.huangyi.adminservice.user.domain.dto.PasswordLoginDTO;
import com.huangyi.adminservice.user.domain.dto.SysUserDTO;
import com.huangyi.adminservice.user.domain.dto.SysUserListReqDTO;
import com.huangyi.adminservice.user.domain.dto.SysUserLoginDTO;
import com.huangyi.adminservice.user.domain.entity.SysUser;
import com.huangyi.adminservice.user.mapper.SysUserMapper;
import com.huangyi.adminservice.user.service.ISysUserService;
import com.huangyi.commoncore.utils.AESUtil;
import com.huangyi.commoncore.utils.BeanCopyUtil;
import com.huangyi.commoncore.utils.VerifyUtil;
import com.huangyi.commondomain.domain.ResultCode;
import com.huangyi.commondomain.exception.ServiceException;
import com.huangyi.commonsecurity.dto.LoginUserDTO;
import com.huangyi.commonsecurity.dto.TokenDTO;
import com.huangyi.commonsecurity.service.TokenService;
import jakarta.annotation.Resource;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;

/**
 * B端用户登录服务实现类
 */
@Service
public class ISysUserServiceImpl implements ISysUserService {

    /**
     * B端用户接口服务类
     */
    @Resource
    private ISysDictionaryService sysDictionaryService;
    /**
     * token 服务类
     */
    @Autowired
    private TokenService tokenService;
    /**
     * 用户接口服务类
     */
    @Autowired
    private SysUserMapper sysUserMapper;

    /**
     * B端用户登录
     *
     * @param passwordLoginDTO B端用户登录DTO
     * @return token信息
     */
    @Override
    public TokenDTO login(PasswordLoginDTO passwordLoginDTO) {
        LoginUserDTO loginUserDTO = new LoginUserDTO();
        // 1 检验手机号是否合规
        if(!VerifyUtil.checkPhone(passwordLoginDTO.getPhone())){
            throw new ServiceException("手机号不合理" ,ResultCode.INVALID_REGION.getCode());
        }
        // 2 查询手机号是否存储 AESUtil.decryptHex(dto.getPassword())
        SysUser sysUser = sysUserMapper.selectByPhoneNumber(AESUtil.encryptHex(passwordLoginDTO.getPhone()));
        if(sysUser == null){
            throw new ServiceException("账号不存在" ,ResultCode.INVALID_REGION.getCode());
        }
        // 3 解密并判断密码是否为空
        String password = AESUtil.decryptHex(passwordLoginDTO.getPassword());
        if(StringUtils.isEmpty(password)){
            throw new ServiceException("密码为空" ,ResultCode.INVALID_REGION.getCode());
        }

        // 4 拿加密后的密码与数据库数据做判断
        String passwordEncrypt = DigestUtil.sha256Hex(password);
        if(!passwordEncrypt.equals(sysUser.getPassword())){
            throw new ServiceException("密码错误" ,ResultCode.INVALID_REGION.getCode());
        }

        // 5 校验状态
        if(sysUser.getStatus().equals("disabled")){
            throw new ServiceException(ResultCode.USER_DISABLE);
        }

        loginUserDTO.setUserId(sysUser.getId());
        loginUserDTO.setUserName(sysUser.getNickName());
        loginUserDTO.setUserFrom("sys");

        return tokenService.createToken(loginUserDTO);

    }

    @Override
    public Long addOrEdit(SysUserDTO sysUserDTO) {
        SysUser sysUser = new SysUser();
        if(sysUserDTO.getUserId() == null){
            // 1 先判断手机号格式是否正确
            if(!VerifyUtil.checkPhone(sysUserDTO.getPhoneNumber())){
                throw new ServiceException("手机格式错误" ,ResultCode.INVALID_REGION.getCode());
            }
            // 2 手机号不能存在
            SysUser sysUser1 = sysUserMapper.selectByPhoneNumber(sysUserDTO.getPhoneNumber());
            if(sysUser1 != null){
                throw new ServiceException("手机号已经存在" ,ResultCode.INVALID_REGION.getCode());
            }
            // 3 检验密码是否合法, 先判空 再检验
            if(StringUtils.isEmpty(sysUserDTO.getPassword()) || !sysUserDTO.checkPassword()){
                throw new ServiceException("密码格式不合法" ,ResultCode.INVALID_REGION.getCode());
            }
            // 4 用户态不存在
            if(StringUtils.isEmpty(sysUserDTO.getIdentity()) || sysDictionaryService.getDicDataByKey(sysUserDTO.getIdentity()) == null){
                throw new ServiceException("用户身份不合法" ,ResultCode.INVALID_REGION.getCode());
            }
            // 5 新增用户逻辑, 设置 PhoneNumber, Password, Identity
            sysUser.setPassword(DigestUtil.sha256Hex(sysUserDTO.getPassword()));
            sysUser.setPhoneNumber(sysUserDTO.getPhoneNumber());
            sysUser.setIdentity(sysUserDTO.getIdentity());


        }
        // 检查用户状态, 是否被弃用
        if (sysDictionaryService.getDicDataByKey(sysUserDTO.getStatus()) == null) {
            throw new ServiceException("用户状态错误", ResultCode.INVALID_PARA.getCode());
        }
        // 允许编辑 or 注册 NickName, Remark, Status, Id, Identity
        sysUser.setNickName(sysUserDTO.getNickName());
        sysUser.setRemark(sysUserDTO.getRemark());
        sysUser.setStatus(sysUserDTO.getStatus());
        sysUser.setId(sysUserDTO.getUserId());
        sysUser.setIdentity(sysUserDTO.getIdentity());

        if(sysUserDTO.getUserId() != null && sysUser.getStatus().equals("disabled")){
            tokenService.delLoginUser(sysUserDTO.getUserId(), "sys");
        }

        sysUserMapper.insertOrUpdate(sysUser);
        return sysUser.getId();
    }


    /**
     * 查询B端用户
     * @param sysUserListReqDTO 用户查询DTO
     * @return B用户列表
     */
    @Override
    public List<SysUserDTO> getUserList(SysUserListReqDTO sysUserListReqDTO) {
        // 声明结果队列
        List<SysUserDTO> result = new ArrayList<SysUserDTO>();
        // 构造查询对象
        SysUser searchSysUser = new SysUser();
        searchSysUser.setId(sysUserListReqDTO.getUserId());
        searchSysUser.setStatus(sysUserListReqDTO.getStatus());
        searchSysUser.setPhoneNumber(AESUtil.encryptHex(sysUserListReqDTO.getPhoneNumber()));
        // 执行查询逻辑
        List<SysUser> sysUsers = sysUserMapper.selectList(searchSysUser);
        //
        for (SysUser sys : sysUsers) {
            SysUserDTO sysUserDTO = new SysUserDTO();
            // 转换逻辑
            sysUserDTO.setIdentity(sys.getIdentity());
            sysUserDTO.setNickName(sys.getNickName());
            sysUserDTO.setPassword(DigestUtil.sha256Hex(sys.getPassword()));
            sysUserDTO.setPhoneNumber(AESUtil.encryptHex(sys.getPhoneNumber()));
            sysUserDTO.setUserId(sys.getId());
            sysUserDTO.setStatus(sys.getStatus());
            sysUserDTO.setRemark(sys.getRemark());
            // 添加到队列
            result.add(sysUserDTO);
        }
        return result;
    }


    /**
     * 获取B端登录用户信息
     * @return B端用户信息VO
     */
    /**
     * 获取B端登录用户信息
     * @return B端用户信息DTO
     */
    @Override
    public SysUserLoginDTO getLoginUser() {
        // 1 获取当前登录用户
        LoginUserDTO loginUserDTO = tokenService.getLoginUser();
        // 2 对象判断
        if (loginUserDTO == null || loginUserDTO.getUserId() == null) {
            throw new ServiceException("用户令牌有误", ResultCode.INVALID_PARA.getCode());
        }
        // 3 查询mysql
        SysUser sysUser = sysUserMapper.selectById(loginUserDTO.getUserId());
        if (sysUser == null) {
            throw new ServiceException("用户不存在", ResultCode.INVALID_PARA.getCode());
        }
        // 4 封装结果
        SysUserLoginDTO sysUserLoginDTO = new SysUserLoginDTO();
        BeanUtils.copyProperties(loginUserDTO, sysUserLoginDTO);
        BeanUtils.copyProperties(sysUser, sysUserLoginDTO);
        return sysUserLoginDTO;
    }
}
